package com.atguigu.java.ai.langchain4j.config;

import com.atguigu.java.ai.langchain4j.store.MongoChatMemoryStore;
import dev.langchain4j.data.document.Document;
import dev.langchain4j.data.document.loader.FileSystemDocumentLoader;
import dev.langchain4j.data.segment.TextSegment;
import dev.langchain4j.memory.chat.ChatMemoryProvider;
import dev.langchain4j.memory.chat.MessageWindowChatMemory;
import dev.langchain4j.model.embedding.EmbeddingModel;
import dev.langchain4j.rag.content.retriever.ContentRetriever;
import dev.langchain4j.rag.content.retriever.EmbeddingStoreContentRetriever;
import dev.langchain4j.service.MemoryId;
import dev.langchain4j.store.embedding.EmbeddingStore;
import dev.langchain4j.store.embedding.EmbeddingStoreIngestor;
import dev.langchain4j.store.embedding.inmemory.InMemoryEmbeddingStore;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.stereotype.Component;

import java.util.Arrays;
import java.util.List;

/**
 * @Author 杨轲
 * @Date 2025/5/9 19:32
 * @Version 1.0
 * @description: null
 */
@Configuration
public class XiaoZhiAgentConfig {

    @Autowired
    MongoChatMemoryStore mongoChatMemoryStore;

    //写一个方法确定对话条数，对话记忆，以及持久化操作
    @Bean
     ChatMemoryProvider xiaoZhiMemory(){
        //MessageWindowChatMemory.builder() 创建一个基于消息窗口的聊天记忆构建器
        return memoryId->
                MessageWindowChatMemory
                        .builder()
                        .id(memoryId)
                        .maxMessages(20)  //20条
                        .chatMemoryStore(mongoChatMemoryStore)  //持久化到mongoDB
                        .build();
    }

    /**
     * 返回一个向量库，千问模型不知道的就去此库中寻找，例如北京协和的交通路线和医生情况，都可以去特定的库中寻找
     * @return
     */
    @Bean
    ContentRetriever contentRetrieverXiaoZhi(){  //E:\SpringCloud\xiaozhi\knowledge
        Document document1 = FileSystemDocumentLoader.loadDocument("E:/SpringCloud/xiaozhi/knowledge/医院信息.md");
        Document document2 = FileSystemDocumentLoader.loadDocument("E:/SpringCloud/xiaozhi/knowledge/科室信息.md");
        Document document3 = FileSystemDocumentLoader.loadDocument("E:/SpringCloud/xiaozhi/knowledge/神经内科.md");

        List<Document> documents = Arrays.asList(document1, document2, document3);
        /**为了简单起见，我们暂时使用基于内存的向量存储 但是不建议在生产中使用基于内存的向量存
        储。可以使用Pinecone作为向量数据库。 但需要配置*/
        InMemoryEmbeddingStore<TextSegment> embeddingStore = new InMemoryEmbeddingStore<>();
        //分割 转向量 存储 都是利用 EmbeddingStoreIngestor.ingest
        EmbeddingStoreIngestor.ingest(documents, embeddingStore);

        //从嵌入存储（EmbeddingStore）里检索和查询内容相关的信息
        return EmbeddingStoreContentRetriever.from(embeddingStore);
    }



//    @Autowired
//    private EmbeddingStore embeddingStore;
//    @Autowired
//    private EmbeddingModel embeddingModel;
//
//    /**
//     * 从peaceone中 同上 嵌入存储中检索内容 有向量相似度匹配
//     * @return
//     */
//    @Bean
//    ContentRetriever contentRetrieverXiaozhiPincone() {
//        // 创建一个 EmbeddingStoreContentRetriever 对象，用于从嵌入存储中检索内容
//        return EmbeddingStoreContentRetriever
//                .builder()
//        // 设置用于生成嵌入向量的嵌入模型
//                .embeddingModel(embeddingModel)
//        // 指定要使用的嵌入存储
//                .embeddingStore(embeddingStore)
//        // 设置最大检索结果数量，这里表示最多返回 1 条匹配结果
//                .maxResults(1)
//        // 设置最小得分阈值，只有得分大于等于 0.2 的结果才会被返回  越大精度越高，1为最大
//                .minScore(0.2)
//        // 构建最终的 EmbeddingStoreContentRetriever 实例
//                .build();
//    }
}
